package com.hqd.ch03.v50.boot.autoconfigure.web.servlet;

import com.hqd.ch03.utils.CollectionUtils;
import com.hqd.ch03.v50.boot.autoconfigure.web.ServerProperties;
import com.hqd.ch03.v50.boot.context.properties.PropertyMapper;
import com.hqd.ch03.v50.boot.web.server.WebServerFactoryCustomizer;
import com.hqd.ch03.v50.boot.web.servlet.WebListenerRegistrar;
import com.hqd.ch03.v50.boot.web.servlet.server.ConfigurableServletWebServerFactory;
import com.hqd.ch03.v50.boot.web.servlet.server.CookieSameSiteSupplier;
import com.hqd.ch03.v50.core.Ordered;

import java.util.Collections;
import java.util.List;

/**
 * 通用配置
 */
public class ServletWebServerFactoryCustomizer
        implements WebServerFactoryCustomizer<ConfigurableServletWebServerFactory>, Ordered {
    /**
     * 配置信息
     */
    private final ServerProperties serverProperties;
    /**
     * 监听类
     */
    private final List<WebListenerRegistrar> webListenerRegistrars;

    private final List<CookieSameSiteSupplier> cookieSameSiteSuppliers;

    public ServletWebServerFactoryCustomizer(ServerProperties serverProperties) {
        this(serverProperties, Collections.emptyList());
    }

    public ServletWebServerFactoryCustomizer(ServerProperties serverProperties,
                                             List<WebListenerRegistrar> webListenerRegistrars) {
        this(serverProperties, webListenerRegistrars, null);
    }

    ServletWebServerFactoryCustomizer(ServerProperties serverProperties,
                                      List<WebListenerRegistrar> webListenerRegistrars, List<CookieSameSiteSupplier> cookieSameSiteSuppliers) {
        this.serverProperties = serverProperties;
        this.webListenerRegistrars = webListenerRegistrars;
        this.cookieSameSiteSuppliers = cookieSameSiteSuppliers;
    }

    @Override
    public int getOrder() {
        return 0;
    }

    @Override
    public void customize(ConfigurableServletWebServerFactory factory) {
        PropertyMapper map = PropertyMapper.get().alwaysApplyingWhenNonNull();
        map.from(this.serverProperties::getPort).to(factory::setPort);
        map.from(this.serverProperties::getAddress).to(factory::setAddress);
        map.from(this.serverProperties.getServlet()::getContextPath).to(factory::setContextPath);
        map.from(this.serverProperties.getServlet()::getApplicationDisplayName).to(factory::setDisplayName);
        map.from(this.serverProperties.getServlet()::isRegisterDefaultServlet).to(factory::setRegisterDefaultServlet);
        map.from(this.serverProperties.getServlet()::getSession).to(factory::setSession);
        map.from(this.serverProperties::getSsl).to(factory::setSsl);
        map.from(this.serverProperties.getServlet()::getJsp).to(factory::setJsp);
        map.from(this.serverProperties::getCompression).to(factory::setCompression);
        map.from(this.serverProperties::getHttp2).to(factory::setHttp2);
        map.from(this.serverProperties::getServerHeader).to(factory::setServerHeader);
        map.from(this.serverProperties.getServlet()::getContextParameters).to(factory::setInitParameters);
        map.from(this.serverProperties.getShutdown()).to(factory::setShutdown);
        for (WebListenerRegistrar registrar : this.webListenerRegistrars) {
            registrar.register(factory);
        }
        if (!CollectionUtils.isEmpty(this.cookieSameSiteSuppliers)) {
            factory.setCookieSameSiteSuppliers(this.cookieSameSiteSuppliers);
        }
    }

}
